#pragma once

#include <AVUICamera.h>
#include <AVUIMatrix3D.h>

namespace AVUI {

class Transform3D;

class ProjectionCamera : public Camera
{
public:
    ProjectionCamera() { };

    DECLARE_ELEMENT(ProjectionCamera, Camera);

    DECLARE_DEPENDENCY_PROPERTY(NearPlaneDistance);
    float get_NearPlaneDistance() { return AVUI::UnboxValue<float>(GetValue(get_NearPlaneDistanceProperty())); }
    void set_NearPlaneDistance(float value) { SetValue(get_NearPlaneDistanceProperty(), AVUI::BoxValue(value)); } 

    DECLARE_DEPENDENCY_PROPERTY(FarPlaneDistance);
    float get_FarPlaneDistance() { return AVUI::UnboxValue<float>(GetValue(get_FarPlaneDistanceProperty())); }
    void set_FarPlaneDistance(float value) { SetValue(get_FarPlaneDistanceProperty(), AVUI::BoxValue(value)); } 

    DECLARE_DEPENDENCY_PROPERTY(Position);
    Point3D get_Position() { return AVUI::UnboxValue<Point3D>(GetValue(get_PositionProperty())); }
    void set_Position(const Point3D& value) { SetValue(get_PositionProperty(), AVUI::BoxValue(value)); } 

    DECLARE_DEPENDENCY_PROPERTY(LookDirection);
    Vector3D get_LookDirection() { return AVUI::UnboxValue<Vector3D>(GetValue(get_LookDirectionProperty())); }
    void set_LookDirection(const Vector3D& value) { SetValue(get_LookDirectionProperty(), AVUI::BoxValue(value)); } 

    DECLARE_DEPENDENCY_PROPERTY(UpDirection);
    Vector3D get_UpDirection() { return AVUI::UnboxValue<Vector3D>(GetValue(get_UpDirectionProperty())); }
    void set_UpDirection(const Vector3D& value) { SetValue(get_UpDirectionProperty(), AVUI::BoxValue(value)); } 

    virtual Matrix3D GetViewMatrix();

    Matrix3D CreateViewMatrix(Transform3D* pTransform, const Point3D& position, const Vector3D& lookDirection, const Vector3D& upDirection);

private:
    static void StaticConstructor();


};


}; // namespace AVUI
